package tests;
import modelo.*;
import junit.framework.TestCase;
import utilitarios.DireccionAbajo;
import utilitarios.DireccionArriba;
import utilitarios.DireccionDerecha;
import utilitarios.DireccionIzquierda;
import utilitarios.PuntoXY;

public class PruebasTanque extends TestCase {

	public void testSiUnTanqueEnemigoSeDestruyeSuArmaCaeAlPisoAlCostadoDerechoDeEl() {

		// ARRANGE
		Escenario escenario = new Escenario(1000, 1000);
		TanqueAlgo tanqueAlgo = new TanqueAlgo(escenario, new PuntoXY(30, 70));
		Cuartel cuartel = new Cuartel(escenario, new PuntoXY(500, 500), tanqueAlgo);
		TanqueEnemigo tanque = new TanqueIFV(escenario, new PuntoXY(30, 30), cuartel);
		tanqueAlgo.girar(new DireccionAbajo());

		escenario.agregarObjeto(tanque);
		escenario.agregarJugador(tanqueAlgo);

		Arma armaDelTanque = tanque.getArma();

		// ACT: Destruyo al tanque
		for (int i = 1; i < 50; i++) {
			tanque.detener();
			tanqueAlgo.disparar();
			escenario.vivir();
		}

		// ASSERT
		assertEquals(0.0, tanque.getResistencia());
		assertEquals(false, escenario.contieneA(tanque));
		assertEquals(true, escenario.contieneA(armaDelTanque));
		assertEquals(60.0, armaDelTanque.getX());
		assertEquals(30.0, armaDelTanque.getY());


	}

	public void testSiUnAlgoTankSeDestruyeSuArmaNoCaeAlPiso() {

		// ARRANGE
		//
		// TANQUE1            ->      TANQUE2		
		Escenario escenario = new Escenario(1000, 1000);
		TanqueAlgo tanque1 = new TanqueAlgo(escenario, new PuntoXY(30, 30));
		tanque1.girar(new DireccionDerecha());
		
		PuntoXY posicionDelTanque2 = new PuntoXY(60, 30);
		TanqueAlgo tanque2 = new TanqueAlgo(escenario, posicionDelTanque2);
		Arma armaDelTanque2 = tanque2.getArma();
		
		escenario.agregarObjeto(tanque1);
		escenario.agregarObjeto(tanque2);
		
		// ACT: Destruyo al tanque2
		for (int i = 1; i < 100; i++) {
			tanque1.disparar();
			escenario.vivir();
		}
		
		// ASSERT
		assertEquals(0.0, tanque2.getResistencia());
		assertEquals(true, posicionDelTanque2.esIgualA(armaDelTanque2.getPosicion()));
		assertEquals(false, escenario.contieneA(tanque2));
		assertEquals(false, escenario.contieneA(armaDelTanque2));
	}
	
	public void testNoSePuedeMoverTanqueADerechaCuandoHayUnaPared() {
		
		// ARRANGE
		Escenario escenario = new Escenario(300, 300);
		TanqueAlgo tanque = new TanqueAlgo(escenario, new PuntoXY(0.5, 0.5));
		ParedDeConcreto pared = new ParedDeConcreto(escenario, new PuntoXY(1.5, 0.5));

		escenario.agregarObjeto(tanque);
		escenario.agregarObjeto(pared);		
		
		// ACT
		tanque.moverEnDireccion(new DireccionDerecha());

		// ASSERT
		assertEquals(0.5, tanque.getFigura().getCentroMasa().getCoordX());
		assertEquals(0.5, tanque.getFigura().getCentroMasa().getCoordY());
	}
	
	public void testNoSePuedeMoverTanqueAbajoCuandoSeAcabaElEscenario() {
		
		// ARRANGE
		Escenario escenario = new Escenario(300, 300);
		TanqueAlgo tanque = new TanqueAlgo(escenario, new PuntoXY(0.5, 0.5));

		escenario.agregarObjeto(tanque);
		
		// ACT		
		tanque.moverEnDireccion(new DireccionAbajo());
		
		// ASSERT
		assertEquals(0.5, tanque.getFigura().getCentroMasa().getCoordX());
		assertEquals(0.5, tanque.getFigura().getCentroMasa().getCoordY());
	}
	
	public void testNoSePuedeMoverTanqueAIzquierdaCuandoSeAcabaElEscenario() {
		
		// ARRANGE
		Escenario escenario = new Escenario(300, 300);
		TanqueAlgo tanque = new TanqueAlgo(escenario, new PuntoXY(0.5, 0.5));
		ParedDeConcreto pared = new ParedDeConcreto(escenario, new PuntoXY(1.5, 0.5));

		escenario.agregarObjeto(tanque);
		escenario.agregarObjeto(pared);
		
		// ACT
		tanque.moverEnDireccion(new DireccionIzquierda());
	
		// ASSERT
		assertEquals(0.5, tanque.getFigura().getCentroMasa().getCoordX());
		assertEquals(0.5, tanque.getFigura().getCentroMasa().getCoordY());
	}
		
	public void testSePuedeMoverTanqueArribaCuandoNoHayObstaculosYNoSeAcabaElEscenario() {	
		
		// ARRANGE
		Escenario escenario = new Escenario(300, 300);
		TanqueAlgo tanque = new TanqueAlgo(escenario, new PuntoXY(30, 30));
		ParedDeConcreto pared = new ParedDeConcreto(escenario, new PuntoXY(60, 30));

		escenario.agregarObjeto(tanque);
		escenario.agregarObjeto(pared);		
		
		// ACT
		tanque.moverEnDireccion(new DireccionArriba());
			
		// ASSERT 
		assertEquals(30.0, tanque.getPosicion().getCoordX());
		assertEquals(31.0, tanque.getPosicion().getCoordY());

	}
	
	public void testNoSePuedeDispararSinMunicion() {
		
		// ARRANGE
		Escenario escenario = new Escenario(300, 300);
		TanqueAlgo tanque = new TanqueAlgo(escenario, new PuntoXY(0.5, 0.5));
		ParedDeConcreto pared = new ParedDeConcreto(escenario, new PuntoXY(1.5, 0.5));

		escenario.agregarObjeto(tanque);
		escenario.agregarObjeto(pared);		
		
		// ACT:  Disparo 101 proyectiles, aunque el tanque solo tiene 100.
		for (int i = 1; i < 101; i++) {
			tanque.disparar();
		}
		
		// ASSERT
		assertEquals(0, tanque.getArma().cantidadBalas());
		
	}

}